package com.xframe.common.core.service;


import com.xframe.common.core.constant.ErrorConstant;
import com.xframe.common.core.dto.AsyncReportDTO;
import com.xframe.common.core.dto.DownFileDto;
import com.xframe.common.core.dto.ErrorCode;
import com.xframe.common.core.dto.QueryExportDTO;
import com.xframe.common.core.exception.BusinessException;
import com.xframe.common.core.export.FactoryByExportFormat;
import com.xframe.common.core.export.IBuilderFileTo;
import com.xframe.domain.ModelRepositoryFactory;
import com.xframe.domain.repository.SysBaseRepository;
import com.xframe.domain.role.IUserCredentials;
import com.xframe.domain.sys.SysModel;
import com.xframe.xdal.core.model.FindOptions;
import com.xframe.xdal.core.model.page.IPagerModel;
import com.xframe.xdal.core.serialize.IJSONSer;
import com.xframe.xdal.core.serialize.JsonConfig;
import com.xframe.xdal.core.serialize.JsonConfigContainer;
import com.xframe.xdal.core.serialize.JsonSerFactory;
import com.xframe.xdal.core.util.redis.RedisAccess;
import lombok.extern.log4j.Log4j2;
import org.springframework.scheduling.annotation.Async;
import org.springframework.scheduling.annotation.EnableAsync;

import java.io.File;
import java.util.Collection;

@Log4j2
public class ExportAsyncService {




//    @Async
//    public void exportToFile(String asyncId,QueryExportDTO queryDTO, FindOptions findOptions,
//                             Class<?> dataType, SysModel sysModel, String downBasePath,
//                             IUserCredentials userCredentials){
//        try {
//            log.info(Thread.currentThread().getName() + " in ExportAsyncService, start run.");
//            AsyncReportDTO asyncReportDTO = RedisAccess.getGetCmd().getObject(asyncId, AsyncReportDTO.class);
//            DownFileDto downFileDto = new DownFileDto();
//            downFileDto.setFileFormat("pdf");
//            downFileDto.setLanguage("cn");
//            downFileDto.setFileName("a77b79af-fa0e-4ab6-8e5b-b4052bce233e");
//            downFileDto.setModelCode("com.xframe.domain.e3sp.basedata.Brand");
//            asyncReportDTO.setData(downFileDto);
//            asyncReportDTO.setRate(100);
//            RedisAccess.getSetCmd().setObject(asyncId, asyncReportDTO, 60 * 10);
//            log.info(Thread.currentThread().getName() + " in ExportAsyncService, set object.");
//            Thread.sleep(2000);
//        } catch (Exception ex) {
//            ex.printStackTrace();
//        }
//
//
//    }


    @Async
    public void exportToFile(String asyncId,QueryExportDTO queryDTO, FindOptions findOptions,
                             Class<?> dataType, SysModel sysModel, String downBasePath,
                             IUserCredentials userCredentials){

        AsyncReportDTO asyncReportDTO = new AsyncReportDTO();
        try {
            log.info(Thread.currentThread().getName() + " in ExportAsyncService, start run.");

            asyncReportDTO = RedisAccess.getGetCmd().getObject(asyncId, AsyncReportDTO.class);
            if(asyncReportDTO == null){
                asyncReportDTO = new AsyncReportDTO();
                throw new BusinessException(ErrorCode.ASYNC_ID_ERROR, ErrorConstant.INTERNAL_SERVER_ERROR_MSG);
            }
            SysBaseRepository repository = ModelRepositoryFactory.builder(sysModel);
            asyncReportDTO.setRate(10);
            asyncReportDTO.setCode(200);
            asyncReportDTO.setStatus("run");
            asyncReportDTO.setMsg("readData");
            RedisAccess.getSetCmd().setObject(asyncId, asyncReportDTO, 60 * 10);
            //Object collection = repository.queryModle(dataType, sysModel, findOptions);
            IPagerModel<Object> collection = repository.queryModleByPage(dataType,sysModel,findOptions);
            asyncReportDTO.setRate(50);
            asyncReportDTO.setCode(200);
            asyncReportDTO.setStatus("run");
            asyncReportDTO.setMsg("procData");
            RedisAccess.getSetCmd().setObject(asyncId, asyncReportDTO, 60 * 10);
            IJSONSer jsonSer = JsonSerFactory.create(sysModel);
            JsonConfig jsonConfig = JsonConfigContainer.getConfigContainer().getJsonConfig(userCredentials.getLanguage(),
                    queryDTO.getVer(), sysModel.getModelCode(), queryDTO.getQueryKey());
            Object dic = jsonSer.toJsonObj(collection.getDataList(), sysModel, userCredentials.getLanguage(), queryDTO.getQueryKey(), queryDTO.getVer());

            asyncReportDTO.setRate(70);
            asyncReportDTO.setCode(200);
            asyncReportDTO.setStatus("run");
            asyncReportDTO.setMsg("createDataFile");
            RedisAccess.getSetCmd().setObject(asyncId, asyncReportDTO, 60 * 10);
            // 生成文件
            File dir = new File("");
            String rootPath = dir.getCanonicalPath() + File.separator;
            log.info(rootPath);
            IBuilderFileTo builderFileTo = FactoryByExportFormat.create(queryDTO.getExportFormat());
            DownFileDto downFileDto = builderFileTo.builderFile(jsonConfig.getJsonModelList(), (Collection) dic,
                    rootPath + downBasePath + File.separator, userCredentials.getLanguage(), queryDTO.getModelCode()
                    , queryDTO.getVer(), queryDTO.getQueryKey());

            asyncReportDTO.setRate(100);
            asyncReportDTO.setCode(200);
            asyncReportDTO.setStatus("complete");
            asyncReportDTO.setMsg("complete");
            asyncReportDTO.setData(downFileDto);

        } catch (BusinessException ex) {
            asyncReportDTO.setRate(100);
            asyncReportDTO.setStatus("error");
            asyncReportDTO.setCode(ex.getCode());
            asyncReportDTO.setMsg(ex.getMessage());
        } catch (Exception ex) {
            asyncReportDTO.setRate(100);
            asyncReportDTO.setCode(500);
            asyncReportDTO.setStatus("error");
            asyncReportDTO.setMsg(ex.getMessage());
        }finally {
            RedisAccess.getSetCmd().setObject(asyncId, asyncReportDTO, 60 * 10);
        }

    }

}
